#!/usr/bin/env python

# Author: Edward Roualdes
#         [2012.11.20]
#         University of Kentucky

import sys
from multiprocessing import Pool
from Bio import SeqIO
from sortBarcode import sortBarcode
from sortLoci import sortLoci
from sanity import sane
import utils
import hap
import structure
import align as a

def init(argv=None):
    if argv is None:
        argv = sys.argv

    print "\nWelcome to NextAllele\n"
    configfile = utils.parseCommandLine(argv)
    opts = sane(configfile)
    return opts

def main(opts = None):

    if opts['sort']:
        utils.mkdir(
            opts['OUTPUTDIRECTORY'], 
            True,
            opt = ("Please specify a different "
                   "OUTPUTDIRECTORY in the CONFIGFILE "))
        srt, c = sortBarcode(
            opts['INPUTFILE'], 
            opts['BARCODEFILE'], 
            opts['trim'])
        srt = sortLoci(srt, opts['BLASTREPORT'], c)
        # write sorted seqs to file
        utils.writeSeqs(srt, opts['OUTPUTDIRECTORY'])
            
    if opts['align']:
        print "Creating primary alignments..."
        p = Pool(processes = opts['cpu'])
        p.map(alignTool, a.files2align(opts['OUTPUTDIRECTORY']))

    # phase: make best quess at exact haplotypes
    # create structure file
    if opts['phase']:
        # phase haplotypes
        hapDir = hap.callHaps(opts['OUTPUTDIRECTORY'], approx = False) 
        # align haplotypes
        p = Pool(processes = opts['cpu'])
        p.map(alignTool, a.files2align(hapDir))

    if opts['structure']:
        structure.mkStruct(opts['OUTPUTDIRECTORY'])

    # unphase: make relatively close quess at haplotypes
    # TBA: create phase file
    if opts['unphase']:
        # phase haplotypes
        hapDir = hap.callHaps(opts['OUTPUTDIRECTORY'], approx = True) 
        # should we align approximated haplotypes?
        # p = Pool(processes = opts['cpu'])
        # p.map(alignTool, a.files2align(hapDir))
        # make phase file

    print "NextAllele finished."

# appease multiprocessing (and GIL)
def alignTool(x):
    return a.aligner(x, opts["ALIGNTOOL"][0], opts["ALIGNTOOL"][1])

if __name__ == '__main__':
    opts = init()
    sys.exit(main(opts))
